package main

import "fmt"

func add(a, b int) int {
	return a + b
}
func sub(a, b int) int {
	return a - b
}

// 回调函数
func calc(a, b int, f FuncType) int {
	return f(a, b)
}

type funcType func(int, int) int

func f1(x, y int) int {
	return x * y
}

// 函数可以作为参数传递，定义参数类型时 指明该参数为函数类型
func f2(f func(int, int) int, a, b int) int {
	return f(a, b)
}

// 函数可以作为返回值
func f3() func(int, int) int {
	return f1
}

func main() {

	var a = f1
	fmt.Printf("type: %T\n", a) // type: func(int, int) int
	fmt.Println(f2(a, 3, 5))    // 15
	var fun2 = f3()
	fmt.Printf("type: %T, call: %d\n", fun2, fun2(2, 5))
	// type: func(int, int) int, call: 10

	var myfun funcType
	myfun = add
	fmt.Println(myfun(1, 2))
	myfun2 := sub
	fmt.Println(myfun2(10, 2))

	fmt.Println(calc(10, 5, add))
	fmt.Println(calc(10, 5, sub))
	fmt.Println(calc(10, 5, myfun))
}
